{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": 3,
   "id": "d3e85f8e-e9bf-4b84-ac8b-bdc6d62d4a1a",
   "metadata": {},
   "outputs": [
    {
     "name": "stdin",
     "output_type": "stream",
     "text": [
      "请输入内容： 1234\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "编码的帧: ['0xca', '0x0', '0x4', '0x31', '0x32', '0x33', '0x34', '0xca', '0xc3']\n",
      "CRC校验失败！\n"
     ]
    }
   ],
   "source": [
    "import struct\n",
    "\n",
    "# 定义帧的常量\n",
    "FRAME_HEADER = b'\\xCA'  # 帧首定界符\n",
    "FRAME_FOOTER = b'\\xC3'  # 帧尾定界符\n",
    "ESCAPE_BYTE = b'\\xCC'    # 转义字节\n",
    "ESCAPED_HEADER = b'\\xCC\\xCA' # 转义后的帧首定界符\n",
    "ESCAPED_ESCAPE = b'\\xCC\\xCC' # 转义后的转义字节\n",
    "\n",
    "class EthernetFrame:\n",
    "    \n",
    "    def __init__(self, data):\n",
    "        self.data = data.encode('utf-8')  # 将字符串数据编码为字节\n",
    "        self.crc = self.calculate_crc()\n",
    "\n",
    "    # 计算简单的校验和作为 CRC\n",
    "    def calculate_crc(self):\n",
    "        return sum(self.data) % 256  # 一个简单的 sum 校验和，实际应用中应采用 CRC 算法\n",
    "\n",
    "    def encode(self):\n",
    "        # 转义数据\n",
    "        escaped_data = bytearray()\n",
    "        for byte in self.data:\n",
    "            if byte == FRAME_HEADER[0]:\n",
    "                escaped_data.extend(ESCAPED_HEADER)\n",
    "            elif byte == ESCAPE_BYTE[0]:\n",
    "                escaped_data.extend(ESCAPED_ESCAPE)\n",
    "            else:\n",
    "                escaped_data.append(byte)\n",
    "\n",
    "        # 编码过程：加入帧首、数据、CRC、帧尾\n",
    "        return (FRAME_HEADER + struct.pack('!H', len(escaped_data)) + \n",
    "                escaped_data + struct.pack('!B', self.crc) + FRAME_FOOTER)\n",
    "\n",
    "    def decode(self, frame):\n",
    "        # 解码过程：移除帧首和帧尾\n",
    "        if frame.startswith(FRAME_HEADER) and frame.endswith(FRAME_FOOTER):\n",
    "            frame_content = frame[1:-2]  # 提取内容，不包括帧首和帧尾\n",
    "            length = struct.unpack('!H', frame_content[:2])[0]  # 提取长度\n",
    "            received_data = frame_content[2:-1]  # 提取数据，最后一字节为CRC\n",
    "\n",
    "            # 计算并验证CRC\n",
    "            received_crc = struct.unpack('!B', frame_content[-1:])[0]  # 接收的CRC\n",
    "            computed_crc = sum(received_data) % 256\n",
    "            \n",
    "            if received_crc != computed_crc:\n",
    "                raise ValueError(\"CRC校验失败！\")\n",
    "\n",
    "            # 反转义数据\n",
    "            decoded_data = bytearray()\n",
    "            i = 0\n",
    "            while i < len(received_data):\n",
    "                if received_data[i] == ESCAPE_BYTE[0]:\n",
    "                    if i + 1 < len(received_data) and received_data[i + 1] == FRAME_HEADER[0]:\n",
    "                        decoded_data.append(FRAME_HEADER[0])\n",
    "                        i += 1  # 跳过下一个字节\n",
    "                    elif i + 1 < len(received_data) and received_data[i + 1] == ESCAPE_BYTE[0]:\n",
    "                        decoded_data.append(ESCAPE_BYTE[0])\n",
    "                        i += 1  # 跳过下一个字节\n",
    "                    else:\n",
    "                        decoded_data.append(received_data[i])  # 其他情况\n",
    "                else:\n",
    "                    decoded_data.append(received_data[i])\n",
    "                i += 1\n",
    "\n",
    "            return decoded_data.decode('utf-8')  # 返回原始数据\n",
    "        else:\n",
    "            raise ValueError(\"无效的帧\")\n",
    "\n",
    "# 主程序\n",
    "if __name__ == \"__main__\":\n",
    "    # 输入内容\n",
    "    input_data = input(\"请输入内容：\")\n",
    "    \n",
    "    # 创建以太网帧编码器\n",
    "    frame = EthernetFrame(input_data)\n",
    "    \n",
    "    # 编码内容\n",
    "    encoded_frame = frame.encode()\n",
    "    print(f\"编码的帧: {[hex(b) for b in encoded_frame]}\")\n",
    "\n",
    "    try:\n",
    "        # 解码内容\n",
    "        decoded_data = frame.decode(encoded_frame)\n",
    "        print(f\"解码后的内容: {decoded_data}\")\n",
    "    except ValueError as e:\n",
    "        print(e)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "93000df9-bb1b-43e1-bb32-4a5786c06494",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.12.4"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
